-
Notifications
You must be signed in to change notification settings - Fork 2.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat(tools): scripts and generator updates to enable SWC transpilation for v9 packages #26527
feat(tools): scripts and generator updates to enable SWC transpilation for v9 packages #26527
Conversation
…ed by v9 packages to transpile based on browser matrix
…ts build to new build:react-components task
Asset size changesSize Auditor did not detect a change in bundle size for any component! Baseline commit: be936b6edefb8d319b6693eb1f36230b716377da (build) |
This pull request is automatically built and testable in CodeSandbox. To see build info of the built libraries, click here or the icon next to each commit SHA. Latest deployment of this branch, based on commit ca8f5dd:
|
Perf Analysis (
|
Scenario | Render type | Master Ticks | PR Ticks | Iterations | Status |
---|---|---|---|---|---|
Avatar | mount | 1344 | 1335 | 5000 | |
Button | mount | 943 | 965 | 5000 | |
Field | mount | 2048 | 2071 | 5000 | |
FluentProvider | mount | 1691 | 1697 | 5000 | |
FluentProviderWithTheme | mount | 657 | 646 | 10 | |
FluentProviderWithTheme | virtual-rerender | 600 | 606 | 10 | |
FluentProviderWithTheme | virtual-rerender-with-unmount | 630 | 646 | 10 | |
InfoButton | mount | 585 | 570 | 5000 | |
MakeStyles | mount | 1902 | 1904 | 50000 | |
Persona | mount | 3083 | 3045 | 5000 | |
SpinButton | mount | 2476 | 2459 | 5000 |
📊 Bundle size reportUnchanged fixtures
|
Perf Analysis (
|
🕵 fluentuiv9 No visual regressions between this PR and main |
Perf Analysis (
|
Scenario | Render type | Master Ticks | PR Ticks | Iterations | Status |
---|---|---|---|---|---|
BaseButton | mount | 1196 | 1181 | 5000 | |
Breadcrumb | mount | 2965 | 2966 | 1000 | |
Checkbox | mount | 2658 | 2635 | 5000 | |
CheckboxBase | mount | 2384 | 2361 | 5000 | |
ChoiceGroup | mount | 4418 | 4461 | 5000 | |
ComboBox | mount | 1270 | 1282 | 1000 | |
CommandBar | mount | 9589 | 9597 | 1000 | |
ContextualMenu | mount | 14224 | 14314 | 1000 | |
DefaultButton | mount | 1368 | 1418 | 5000 | |
DetailsRow | mount | 3453 | 3509 | 5000 | |
DetailsRowFast | mount | 3500 | 3494 | 5000 | |
DetailsRowNoStyles | mount | 3307 | 3357 | 5000 | |
Dialog | mount | 3086 | 3142 | 1000 | |
DocumentCardTitle | mount | 577 | 582 | 1000 | |
Dropdown | mount | 3213 | 3254 | 5000 | |
FocusTrapZone | mount | 2055 | 2068 | 5000 | |
FocusZone | mount | 1961 | 1987 | 5000 | |
GroupedList | mount | 52756 | 59158 | 2 | |
GroupedList | virtual-rerender | 24653 | 24658 | 2 | |
GroupedList | virtual-rerender-with-unmount | 93195 | 93186 | 2 | |
GroupedListV2 | mount | 561 | 561 | 2 | |
GroupedListV2 | virtual-rerender | 537 | 555 | 2 | |
GroupedListV2 | virtual-rerender-with-unmount | 548 | 573 | 2 | |
IconButton | mount | 1929 | 1930 | 5000 | |
Label | mount | 734 | 738 | 5000 | |
Layer | mount | 4350 | 4265 | 5000 | |
Link | mount | 833 | 834 | 5000 | |
MenuButton | mount | 1673 | 1683 | 5000 | |
MessageBar | mount | 2257 | 2257 | 5000 | |
Nav | mount | 3267 | 3591 | 1000 | |
OverflowSet | mount | 1342 | 1379 | 5000 | |
Panel | mount | 2525 | 2546 | 1000 | |
Persona | mount | 1303 | 1341 | 1000 | |
Pivot | mount | 1629 | 1650 | 1000 | |
PrimaryButton | mount | 1523 | 1536 | 5000 | |
Rating | mount | 6987 | 7023 | 5000 | |
SearchBox | mount | 1491 | 1512 | 5000 | |
Shimmer | mount | 2882 | 2838 | 5000 | |
Slider | mount | 2073 | 2104 | 5000 | |
SpinButton | mount | 5035 | 4673 | 5000 | |
Spinner | mount | 810 | 805 | 5000 | |
SplitButton | mount | 3114 | 3111 | 5000 | |
Stack | mount | 833 | 850 | 5000 | |
StackWithIntrinsicChildren | mount | 2309 | 2299 | 5000 | |
StackWithTextChildren | mount | 4748 | 4745 | 5000 | |
SwatchColorPicker | mount | 10462 | 10481 | 5000 | |
TagPicker | mount | 2609 | 2611 | 5000 | |
TeachingBubble | mount | 85666 | 87234 | 5000 | |
Text | mount | 799 | 815 | 5000 | |
TextField | mount | 1567 | 1595 | 5000 | |
ThemeProvider | mount | 1525 | 1510 | 5000 | |
ThemeProvider | virtual-rerender | 1095 | 1113 | 5000 | |
ThemeProvider | virtual-rerender-with-unmount | 2142 | 2160 | 5000 | |
Toggle | mount | 1115 | 1106 | 5000 | |
buttonNative | mount | 543 | 556 | 5000 |
… targets always take precedence
Had a few hiccups with this as it increased bundle size for the v9 packages. Finally got the correct setup for the |
🕵 fluentuiv8 No visual regressions between this PR and main |
@TristanWatanabe there is a difference in the diff that no one noticed: Considering an amount of object spreads it's a bummer that it gets transformed. I checked that we should always fall into the path with EDIT: Looks like bf390c0 fixed that, so ignore it 🐱 |
@layershifter Yup we caught that when the bundle size ballooned due to the helper function being used for the spread. @spmonahan actually filed an issue to swc regarding the object spread: swc-project/swc#7044 |
🕵 FluentUI-v0 No visual regressions between this PR and main |
@TristanWatanabe Looks like the PR for the issue was closed so I'm not sure if a fix is imminent. However, in looking at the PR it seems like is a (undocumented?) |
@spmonahan I just tried adding * runtime code filtering props in this function.
*
* @param state - State including slot definitions
* @returns An object containing the `slots` map and `slotProps` map.
*/
function(state) {
const slots = {}, slotProps = {}, slotNames = Object.keys(state.components);
for (const slotName of slotNames) {
const [slot, props] = getSlot(state, slotName);
slots[slotName] = slot, slotProps[slotName] = props;
}
return {
slots: slots,
slotProps: slotProps
};
}(state);
/*#__PURE__*/
return external_React_namespaceObject.createElement(slots.root, slotProps.root);
}, __GLOBAL__ = "undefined" == typeof window ? __webpack_require__.g : window; |
Interesting. I wonder if maybe that's even more desirable behavior than directly using spread? Just passing the props seems to be the "default" Babel behavior. @Hotell / @layershifter do you know why we used spread with the old/current build tooling? |
That's interesting: // INPUT
import * as React from 'react'
function App(props) {
return <div {...props} />
}
function App2(props) {
return <div {...props} aria-label="foo" />
} ⬇️⬇️⬇️ // OUTPUT BY TS
import * as React from 'react';
function App(props) {
return React.createElement("div", { ...props });
}
function App2(props) {
return React.createElement("div", { ...props, "aria-label": "foo" });
} // OUTPUT BY BABEL
import * as React from 'react';
function App(props) {
return /*#__PURE__*/React.createElement("div", props);
}
function App2(props) {
return /*#__PURE__*/React.createElement("div", _extends({}, props, {
"aria-label": "foo"
}));
} AFAIR it's okay to avoid spread there as React does a loop through |
To add on to this, the // SWC output via https://swc.rs/playground
import * as React from 'react';
function App(props) {
return /*#__PURE__*/ React.createElement("div", props);
}
function App2(props) {
return /*#__PURE__*/ React.createElement("div", {
...props,
"aria-label": "foo"
});
} |
Just so I'm clear, |
Haven't investigated it yet but it's now consistently failing for ssr-tests when I fully tested it with all v9 packages using |
… of using Object.assign
Hmm I was able to get a good build this time around. I wasn't able to repro the puppeteer navigation timeout error that was popping up in CI on my local machine so it was hard to debug. The ssr-tests-v9 timeout errors may be completely unrelated to the |
I posted a follow up question on my thread for the SWC folks to make sure |
Looks like we should use it. |
Released a new nightly version ( |
Changes:
Scripts:
swc.ts
file which invokes the SWC CLI that allows us to transpile our code based on a browser matrix target. Browser matrix and other necessary configs are provided by the.swcrc
file added to each v9 package.swc
related just-tasks to preset just-tasks.build:react-components
just-task to be used by v9 packages. The key difference here and the normalbuild
task is that this now splits up transpilation and api-generation as two separate tasks. The transpilation portion uses SWC to transpile code down and then makes use ofbabel
to transform griffel related code. Transpiling tocjs
oramd
will now use the already transpiledesm
code output from SWC as a workaround to the issue where ourgriffel
babel-preset is unable to directly parsecjs
code transpiled by SWC (tracking PR of ongoing work for this). This method allows for@griffel/babel-preset
to still parse code as expected since it has no trouble transformingesm
transpiled code from SWC. The api-generation task now generates TSdts
files and then runs the api-extractor thus allowing as to do both transpilation and api-generation in PARALLEL, speeding up build time.After SWC transpiles code with our full browser support matrix which includes
nullish coallescing
, code is not transformed:After SWC transpiles files with a browser matrix target that doesn't support
nullish coalescing
, nullish coalescing syntax is transformed:Generators:
migrate-converged-pkg
workspace generator will now add an.swcrc
file to all v9 packages pre-populated with our Full Browser Support Matrixmigrate-converged-pkg
will now update thejust.config.ts
file of all v9 packages to map newbuild:react-components
just-task to act as thebuild
task. This will essentially "opt-in" these packages to the new browser matrix based transpilation approach with SWC.PR with migration applied to v9 packages: #26528
Related Issue(s)